<template>
    <el-row class="contain-box">
        <site-nav/>
        <div class="view-body">
            <el-row>
                <el-form class="inline-form" inline>
                    <el-form-item>
                        <el-button @click="addEntity" type="primary"><i class="el-icon-plus el-icon--left"/>添加菜单
                        </el-button>
                    </el-form-item>
                </el-form>
            </el-row>
            <el-row>
                <el-table :data="tree" border ref="table" row-key="menuId" size="small">
                    <el-table-column fixed label="菜单名称" prop="displayName" width="180"/>
                    <el-table-column label="菜单key" prop="menuKey"/>
                    <el-table-column label="访问路径" prop="path"/>
                    <el-table-column label="域" prop="domain"/>
                    <el-table-column label="模块名" prop="module"/>
                    <el-table-column label="激活路径">
                        <template slot-scope="scope">
                            {{scope.row.activeKey ? scope.row.activeKey : '-'}}
                        </template>
                    </el-table-column>
                    <el-table-column label="组件路径" prop="componentPath"/>
                    <el-table-column label="图标" width="50" align="center">
                        <template slot-scope="scope">
                            <el-image :src="$getImageUrl(scope.row.icon)"
                                      class="cover"
                                      fit="contain"
                                      v-if="scope.row.icon"/>
                        </template>
                    </el-table-column>
                    <el-table-column label="显示" width="50" align="center">
                        <template slot-scope="scope">
                            <commons-enable :value="!scope.row.hidden"/>
                        </template>
                    </el-table-column>
                    <el-table-column label="叶节点" width="57" align="center">
                        <template slot-scope="scope">
                            <commons-enable :value="scope.row.leaf"/>
                        </template>
                    </el-table-column>
                    <el-table-column label="重定向" width="57" align="center">
                        <template slot-scope="scope">
                            <commons-enable :value="scope.row.redirect"/>
                        </template>
                    </el-table-column>
                    <el-table-column label="排序" prop="orderNum" width="50"/>
                    <el-table-column fixed="right" label="操作" width="240">
                        <template slot-scope="scope">
                            <el-button @click.stop="addEntity(scope.row)" size="mini" type="primary">添加下级
                            </el-button>
                            <el-button @click.stop="updateEntity(scope.row)" size="mini">修改</el-button>
                            <el-button v-if="!(scope.row.children && scope.row.children.length > 0)"
                                       @click.stop="deleteEntity(scope.row)"
                                       size="mini"
                                       type="danger">删除
                            </el-button>
                        </template>
                    </el-table-column>
                </el-table>
            </el-row>
            <el-dialog :before-close="dialogClose" :title="dialog.isAdd ? '新增菜单' : '修改菜单'" :visible.sync="dialog.show"
                       class="dialog">
                <el-form :model="info" :rules="rules" label-width="120px" ref="form" size="small">
                    <el-form-item label="上级菜单" prop="parentId">
                        <el-cascader :options="list" :props="props" class="input" clearable filterable
                                     v-model="info.parentId"/>
                    </el-form-item>
                    <el-form-item label="菜单Key" prop="menuKey">
                        <el-input type="text" v-model="info.menuKey"/>
                    </el-form-item>
                    <el-form-item label="菜单名称" prop="displayName">
                        <el-input type="text" v-model="info.displayName"/>
                    </el-form-item>
                    <el-form-item label="域" prop="domain">
                        <el-input type="text" v-model="info.domain"/>
                    </el-form-item>
                    <el-form-item label="模块名" prop="module">
                        <el-input type="text" v-model="info.module"/>
                    </el-form-item>
                    <el-form-item label="访问路径" prop="path">
                        <el-input type="text" v-model="info.path"/>
                    </el-form-item>
                    <el-form-item label="激活菜单Key" prop="activeKey">
                        <el-input type="text" v-model="info.activeKey"/>
                    </el-form-item>
                    <el-form-item label="组件路径" prop="componentPath">
                        <el-input type="text" v-model="info.componentPath"/>
                    </el-form-item>
                    <el-form-item label="图标">
                        <el-image :src="$getImageUrl(iconCache)"
                                  class="cover"
                                  fit="contain"
                                  v-if="iconCache"/>
                    </el-form-item>
                    <el-form-item label="">
                        <upload-single :on-success="coverUploadHandler" accept="image/*" class="cover-uploader uploader-button"
                                       path="menuIcon"/>
                        <el-button v-if="iconCache" @click="removeIcon()" class="uploader-button" type="danger">删除
                        </el-button>
                    </el-form-item>
                    <el-form-item label="显示">
                        <el-radio-group v-model="info.hidden">
                            <el-radio :label="false">是</el-radio>
                            <el-radio :label="true">否</el-radio>
                        </el-radio-group>
                    </el-form-item>
                    <el-form-item label="叶节点">
                        <el-radio-group v-model="info.leaf">
                            <el-radio :label="false">否</el-radio>
                            <el-radio :label="true">是</el-radio>
                        </el-radio-group>
                    </el-form-item>
                    <el-form-item label="重定向">
                        <el-radio-group v-model="info.redirect">
                            <el-radio :label="false">否</el-radio>
                            <el-radio :label="true">是</el-radio>
                        </el-radio-group>
                    </el-form-item>
                    <el-form-item label="排序值">
                        <el-input type="number" v-model="info.orderNum"/>
                    </el-form-item>
                </el-form>
                <div class="dialog-footer" slot="footer">
                    <el-button @click="dialogClose" size="mini">取 消</el-button>
                    <el-button :loading="dialog.submitting" @click="dialogSubmit" size="mini" type="primary">确 定
                    </el-button>
                </div>
            </el-dialog>
        </div>
    </el-row>
</template>
<script lang="ts">
  import MenuApi from '@/api/user/menuApi';
  import DialogInfo from '@/structure/dialogInfo';
  import FileInfo from '@/structure/fileInfo';
  import FormRules from '@/structure/formRules';
  import Menu from '@/structure/menu';
  import OtpUtils from '@/utils/otp';
  import {ElForm} from 'element-ui/types/form';
  import {Component, Vue} from 'vue-property-decorator';

  const EmptyMenu = new Menu();
  EmptyMenu.menuId = '0';
  EmptyMenu.displayName = '无';

  @Component
  export default class Page extends Vue {
    public iconCache?: string = '';
    public tree: Menu[] = [];
    public list: Menu[] = [];
    public dialog: DialogInfo = new DialogInfo();
    public info: Menu = new Menu();
    public rules: FormRules = {
      parentId: [
        {
          required: true,
          message: '请选择上级菜单'
        }
      ],
      menuKey: [
        {
          required: true,
          message: '请输入菜单Key'
        }
      ],
      displayName: [
        {
          required: true,
          message: '请输入菜单名称'
        }
      ],
      path: [
        {
          required: true,
          message: '请输入访问路径'
        }
      ],
      componentPath: [
        {
          required: true,
          message: '请输入组件路径'
        }
      ]
    };
    public props = {
      value: 'menuId',
      label: 'displayName',
      expandTrigger: 'hover',
      checkStrictly: true,
      emitPath: false
    };

    public created(): void {
      this.getDataList();
    }

    public getDataList(): void {
      if (this.$refs.table) {
        this.$contractTree(this.$refs.table);
      }

      MenuApi.tree().then((res) => {
        this.tree = res;
        this.list = [EmptyMenu].concat(res);
        this.$nextTick(() => {
          this.$expandTree(this.$refs.table);
        });
      });
    }

    public addEntity(info: Menu): void {
      this.dialog.isAdd = true;
      this.dialog.show = true;
      this.info = {
        hidden: false,
        leaf: false,
        redirect: false,
        parentId: info && info.menuId ? info.menuId : '0',
        componentPath: 'Root'
      } as Menu;

      this.$nextTick(() => {
        (this.$refs.form as ElForm).clearValidate();
      });
    }

    public updateEntity(info: Menu): void {
      this.info = {...info};
      this.iconCache = info.icon;
      this.dialog.isAdd = false;
      this.dialog.show = true;

      this.$nextTick(() => {
        (this.$refs.form as ElForm).clearValidate();
      });
    }

    public deleteEntity(info: Menu): void {
      this.$confirm('是否删除该菜单?', '删除菜单', {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning'
      }).then(() => {
        MenuApi.delete(info.menuId).then(() => {
          this.getDataList();
          this.$message.success('删除成功!');
        });
      });
    }

    public dialogClose(): void {
      this.dialog.show = false;
      this.info = new Menu();
      (this.$refs.form as ElForm).resetFields();
    }

    public dialogSubmit(): void {
      if (this.dialog.submitting) {
        return;
      }

      (this.$refs.form as ElForm).validate((valid) => {
        if (!valid) {
          return false;
        }

        this.dialog.submitting = true;

        const func = this.dialog.isAdd ? MenuApi.save : MenuApi.update;
        const msg = this.dialog.isAdd ? '添加菜单成功' : '编辑菜单成功';

        func.call(MenuApi, this.info).then(() => {
          this.getDataList();
          this.dialogClose();
          this.dialog.submitting = false;
          this.$message.success(msg);
        }).catch(({errorCode, message}) => {
          this.dialog.submitting = false;
          if (errorCode === 901) {
            OtpUtils.enableOtp()
              .then(() => this.dialogSubmit())
              .catch(() => this.dialogClose());
          } else if (errorCode >= 900 && errorCode < 1000) {
            this.$message.error(message);
          }
        });
      });
    }

    public coverUploadHandler(res: FileInfo): void {
      this.info.icon = res.webPath;
      this.iconCache = res.webPath;
    }

    public removeIcon(): void {
      this.info.icon = '';
      this.iconCache = '';
    }
  }
</script>
<style lang="scss" scoped>
    .input {
        width: 100%;
    }

    .icon-input {
        width: 80%;
    }

    .uploader-button {
        display: inline-block;
        margin-right: 20px;

        &:last-child{
            margin-right: 0;
        }
    }
</style>
